package web

import (
	"errors"
	"fmt"
	"github.com/globalsign/mgo"
	"jgt-oper/src/bll"
	"jgt-oper/src/context"
	"jgt-oper/src/schema"
	"jgt-oper/src/util"
	"strings"
	"time"
)

// NoticeController 通知发布控制器
type NoticeController struct {
	NoticeBll     *bll.Notice     `inject:""`
	UserBll       *bll.User       `inject:""`
	EnterpriseBll *bll.Enterprise `inject:""`
}

// Create 创建通知
func (a *NoticeController) Create(ctx *context.Context) error {
	ctx.WriteOperateLog("NoticeController.Create", "通知发布管理-创建通知")
	//	获取参数
	params := new(schema.NoticeCParams)
	if err := ctx.ParseJSON(params); err != nil {
		return ctx.ResErrBadRequest(err)
	}
	//	构造存储结构
	item := new(schema.Notice)
	item.ID = 0
	item.RecordID = util.UUID()
	item.Creator = ctx.GetUserID()
	item.Created = time.Now().Unix()
	item.Deleted = 0
	//
	item.NoticeTitle = params.NoticeTitle
	item.ReceiveGroupType = params.ReceiveGroupType
	item.ReceiveGroup = params.ReceiveGroup
	item.NoticeMode = params.NoticeMode
	item.NoticeContent = params.NoticeContent
	item.Status = 1

	err := a.NoticeBll.Create(item)
	if err != nil {
		return ctx.ResErrInternalServer(err)
	}
	//	TODO 校验是否发送通知
	if params.MessageFrequency != 0 {
		//item.SendTime = time.Now().Unix()
		//item.NoticeSender = ctx.GetUserID()
		//	如果发送的话，更新通知文档的信息:发送人、发送时间

		info := make(map[string]interface{})
		info["notice_sender"] = ctx.GetUserID()
		info["send_time"] = time.Now().Unix()
		info["status"] = 2

		err := a.NoticeBll.Update(item.RecordID, info)
		if err != nil {
			return ctx.ResErrInternalServer(err)
		}
	}

	return ctx.ResOK()

}

// Get 查询通知
func (a *NoticeController) Get(ctx *context.Context) error {
	ctx.WriteOperateLog("NoticeController.Get", "通知发布管理-查询通知详情")
	item, err := a.NoticeBll.Get(ctx.Param("id"))
	if err != nil {
		return ctx.ResErrInternalServer(err)
	}
	result := make(map[string]interface{})
	result["record_id"] = item.RecordID
	result["notice_title"] = item.NoticeTitle
	result["receive_group_type"] = item.ReceiveGroupType
	result["receive_group"] = item.ReceiveGroup
	result["notice_mode"] = item.NoticeMode
	modeList := make([]string, 0)
	switch item.NoticeMode {
	case 1:
		modeList = append(modeList, "推送通知")
	case 2:
		modeList = append(modeList, "短信通知")
	case 3:
		modeList = append(modeList, "推送通知")
		modeList = append(modeList, "短信通知")
	}
	result["notice_mode_name"] = modeList
	result["notice_content"] = item.NoticeContent
	result["send_time"] = item.SendTime
	result["creator"] = item.Creator
	//	创建人名字
	user, err := a.UserBll.Get(item.Creator)
	if err != nil {
		return ctx.ResErrInternalServer(err)
	}
	if user == nil {
		return ctx.ResErrInternalServer(errors.New("创建人信息查询错误"))
	}
	result["creator_name"] = user.Nickname

	//	发送人名字
	result["notice_sender"] = item.NoticeSender
	result["notice_sender_name"] = ""
	if item.NoticeSender != "" {
		sendUser, err := a.UserBll.Get(item.NoticeSender)
		if err != nil {
			return ctx.ResErrInternalServer(err)
		}
		if sendUser == nil {
			return ctx.ResErrInternalServer(errors.New("发送人信息未找到"))
		}
		result["notice_sender_name"] = sendUser.Nickname
	}

	result["created"] = item.Created
	result["status"] = item.Status
	return ctx.ResSuccess(result)
}

// QueryPage 查询分页
func (a *NoticeController) QueryPage(ctx *context.Context) error {
	ctx.WriteOperateLog("NoticeController.QueryPage", "通知发布管理-查询分页数据")
	pageIndex, pageSize := ctx.GetPageIndex(), ctx.GetPageSize()
	params := new(schema.NoticeQParams)
	params.NoticeTitle = ctx.Query("notice_title")
	params.ReceiveGroupType = ctx.QueryInt("receive_group_type")
	s := ctx.Query("receive_group")
	//	检测是否为空
	if s == "" {
		params.ReceiveGroup = make([]string, 0)
	} else {
		params.ReceiveGroup = strings.Split(s, ",")
	}

	params.MessageMode = ctx.QueryInt("message_mode")
	params.PushMode = ctx.QueryInt("push_mode")
	params.NoticeContent = ctx.Query("notice_content")
	params.Status = ctx.QueryInt("status")
	params.StartTime = ctx.QueryInt64("start_time")
	params.EndTime = ctx.QueryInt64("end_time")

	total, items, err := a.NoticeBll.QueryPage(params, pageIndex, pageSize)
	if err != nil {
		return ctx.ResErrInternalServer(err)
	}

	list := make([]map[string]interface{}, 0)
	for _, item := range items {
		//	初始化盛放数据的map
		tempMap := make(map[string]interface{})
		//	装填返回的数据
		tempMap["record_id"] = item.RecordID
		tempMap["notice_title"] = item.NoticeTitle
		tempMap["receive_group_type"] = item.ReceiveGroupType
		tempMap["receive_group"] = item.ReceiveGroup
		modeList := make([]string, 0)
		switch item.NoticeMode {
		case 1:
			modeList = append(modeList, "推送通知")
		case 2:
			modeList = append(modeList, "短信通知")
		case 3:
			modeList = append(modeList, "推送通知")
			modeList = append(modeList, "短信通知")
		}
		tempMap["notice_mode_name"] = modeList
		tempMap["notice_mode"] = item.NoticeMode
		tempMap["notice_content"] = item.NoticeContent
		tempMap["creator"] = item.Creator
		tempMap["created"] = item.Created
		tempMap["notice_sender"] = item.NoticeSender
		tempMap["send_time"] = item.SendTime
		tempMap["status"] = item.Status
		//	创建人人名字
		userItem, err := a.UserBll.Get(item.Creator)
		if err != nil {
			return ctx.ResErrInternalServer(err)
		}
		tempMap["creator_name"] = userItem.Nickname
		//	发送人名字
		userSend, err := a.UserBll.Get(item.Creator)
		if err != nil {
			return ctx.ResErrInternalServer(err)
		}
		tempMap["notice_sender_name"] = userSend.Nickname
		//	接收对象名字
		switch item.ReceiveGroupType {
		case 1:
			tempMap["receive_group_name"] = "所有企业管理员"
		case 2:
			tempMap["receive_group_name"] = "所有用户"
		case 3:
			tempMap["receive_group_name"] = "所有游客"
		case 4:
			tempMap["receive_group_name"] = "所有未认证用户"
		case 5:
			tempMap["receive_group_name"] = "所有认证用户"
		case 6, 7:
			//	接收对象为企业的时候，将企业的名字装进去
			nameArray := make([]string, 0)
			for _, enterpriseID := range item.ReceiveGroup {
				enterpriseItem, err := a.EnterpriseBll.Get(enterpriseID)
				if err != nil {
					return ctx.ResErrInternalServer(err)
				}
				nameArray = append(nameArray, enterpriseItem.Name)
			}
			nameStr := strings.Join(nameArray, ",")
			tempMap["receive_group_name"] = nameStr
		case 8:
			//	接收对象为指定用户的时候，将用户名字装进去
			nameArray := make([]string, 0)
			for _, userID := range item.ReceiveGroup {
				userItem, err := a.UserBll.Get(userID)
				if err != nil && err != mgo.ErrNotFound {
					return ctx.ResErrInternalServer(err)
				}
				//	校验用户信息是否有效
				if err == mgo.ErrNotFound || userItem == nil {
					nameArray = append(nameArray, fmt.Sprintf("[用户id失效:%s]", userID))
					continue
				}
				nameArray = append(nameArray, userItem.Nickname)
			}
			nameStr := strings.Join(nameArray, ",")
			tempMap["receive_group_name"] = nameStr
		}
		//	将单个通知详情添加进数组
		list = append(list, tempMap)
	}

	result := map[string]interface{}{
		"list": list,
		"pagination": map[string]interface{}{
			"total":    total,
			"current":  pageIndex,
			"pageSize": pageSize,
		},
	}
	return ctx.ResSuccess(result)
}

// Update 更新
func (a *NoticeController) Update(ctx *context.Context) error {
	ctx.WriteOperateLog("NoticeController.Update", "通知发布管理-更新数据")
	params := new(schema.NoticeUParams)
	if err := ctx.ParseJSON(params); err != nil {
		return ctx.ResErrBadRequest(err)
	}
	info := make(map[string]interface{})
	info["notice_title"] = params.NoticeTitle
	info["receive_group_type"] = params.ReceiveGroupType
	info["receive_group"] = params.ReceiveGroup
	info["notice_mode"] = params.NoticeMode
	info["notice_content"] = params.NoticeContent

	err := a.NoticeBll.Update(params.RecordID, info)
	if err != nil {
		return ctx.ResErrInternalServer(err)
	}
	//	TODO	校验是否发送推送消息或者短信消息
	if params.MessageFrequency != 0 {
		//item.SendTime = time.Now().Unix()
		//item.NoticeSender = ctx.GetUserID()
		//	如果发送的话，更新通知文档的信息:发送人、发送时间

		//	更新信息
		info := make(map[string]interface{})
		info["notice_sender"] = ctx.GetUserID()
		info["send_time"] = time.Now().Unix()
		info["status"] = 2

		err := a.NoticeBll.Update(params.RecordID, info)
		if err != nil {
			return ctx.ResErrInternalServer(err)
		}
	}
	return ctx.ResOK()
}

// Delete 标记删除
func (a *NoticeController) Delete(ctx *context.Context) error {
	ctx.WriteOperateLog("NoticeController.Update", "通知发布管理-更新数据")
	recordID := ctx.Param("id")
	info := make(map[string]interface{})
	info["deleted"] = time.Now().Unix()
	info["status"] = 3

	err := a.NoticeBll.Update(recordID, info)
	if err != nil {
		return ctx.ResErrInternalServer(err)
	}
	return ctx.ResOK()
}
